<?php
/**
 * ws相关处理
 */
namespace app\ws\controller;
use app\api\business\CommonBus as CommonBus;
use think\facade\Log;
use app\common\model\redis\RedisModel;
use app\common\lib\Time;
class GatewayService
{
    public $client_id = '';
    public $token = '';
    // gate 闸机标识 events Gateway事件  heartbeat 心跳 broadcast 统一广播
    public $make = ['gate'=>'gate','events'=>'events','heartbeat'=>'heartbeat', 'broadcast'=>'broadcast'];

    /**
     * 判断token是否有效
     * @param $client_id
     * @param $token
     */
    public function tokenVerification($client_id,$token)
    {
        try{
            $this->token = $token;
            $this->client_id = $client_id;
            $RedisModel = new RedisModel();
            $info = $RedisModel->getValue(config("redis.token_pre").$token);
            $info = json_decode($info,true);
            if(empty($info)){
                return false;
            }

            // 确定是设备连接还是前端连接
            if(isset($info['serial_number'])){
                $unique_code = $info['serial_number'];
            }else{
                $unique_code = $info['user_number'];
            }
            $obj = new CommonBus('Relationship');
            $res = $obj->getFieldInfo('unique_code',$unique_code,true);
            if($res){
                $data = ['id'=>$res['id'],'connect_id'=>$client_id,'token'=>$token,'is'=>1];
                $obj->updateData($data);
            }else{
                $data = ['connect_id'=>$client_id,'unique_code'=>$unique_code,'token'=>$token,'status'=>1,'is'=>1];
                $obj->addData($data);
            }
            return true;
        }catch (\Exception $e){
            logWrite('GatewayService,tokenVerification', $client_id.'=>'.$e->getMessage(),__FILE__ );
            $this->wsReturnError($client_id);
        }
    }


    /**
     * 客户端退出
     * @param $client_id
     */
    public function logout($client_id){
        try{
            $obj = new CommonBus('Relationship');
            $res = $obj->getFieldInfo('connect_id',$client_id,true);
            if($res){
                $obj->deleteData($res['id']);
            }
        }catch (\Exception $e){
            logWrite('GatewayService,logout', $client_id.'=>'.$e->getMessage(),__FILE__ );
            $this->wsReturnError($client_id);
        }
    }

    /**
     * 心跳检测
     * @param $client_id
     * @param $params
     */
    public function heartbeat($client_id){
        try{
            $obj = new CommonBus('Relationship');
            $res = $obj->getFieldInfo('connect_id',$client_id,true);
            if(empty($res)){
                $this->wsReturnError($client_id,400,[],'连接ID有误！');
            }
            $RedisModel = new RedisModel();
            $token_pre = $RedisModel->getValue(config("redis.token_pre").$res['token']);
            if($token_pre){
                $info = json_decode($token_pre,true);
                // 客户端
                if(isset($info['serial_number'])){
                    $RedisModel->setexValue(config("redis.token_id").$info['serial_number'],$res['token'],Time::userLoginExpiresTime());
                    // 保存用户token的相关数据
                    $RedisModel->setexValue(config("redis.token_pre").$res['token'],$token_pre,Time::userLoginExpiresTime());
                }else{
                    $userInfo = json_decode($token_pre,true);
                    $RedisModel->setexValue(config("redis.token_id").$userInfo['id'],$res['token'],Time::userLoginExpiresTime());
                    $RedisModel->setexValue(config("redis.token_pre").$res['token'],$token_pre,Time::userLoginExpiresTime());
                }
                $this->wsReturnResult($client_id,[],'心跳刷新！',$this->make['heartbeat']);
            }else{
                $this->wsReturnError($client_id,400,[],'token有误！');
            }
        }catch (\Exception $e){
            logWrite('GatewayService,logout', $client_id.'=>'.$e->getMessage(),__FILE__ );
            $this->wsReturnError($client_id);
        }
    }


    /**
     * 广播所有客户端
     * @param $client_id
     * @throws \Exception
     */
    public function broadcastResults($data=[],$message='ok',$mark=''){
        $result = ['code'=>config("config.code.success"),'data'=>$data,'message'=>$message,'mark'=>$mark];
        \app\ws\controller\gatewayworker\Events::sendToAll(json_encode($result));
    }

    /**
     * WS成功返回
     * @param $client_id
     */
    public function wsReturnResult($client_id,$data=[],$message='ok',$mark=''){
        $result = ['code'=>config("config.code.success"),'data'=>$data,'message'=>$message,'mark'=>$mark];
        \app\ws\controller\gatewayworker\Events::sendToClient($client_id,json_encode($result));
    }

    /**
     * WS错误返回
     * @param $client_id
     */
    public function wsReturnError($client_id, $code ='',$data=[],$message='error',$mark=''){
        if(empty($code)){
            $code = config("config.code.error");
        }
        $result = ['code'=>$code,'data'=>$data,'message'=>$message,'mark'=>$mark];
        \app\ws\controller\gatewayworker\Events::sendToClient($client_id,json_encode($result));
    }
}
